package com.xunk.equipment.service.zhijia.util;

import com.xunk.common.core.utils.SpringUtils;
import com.xunk.common.core.utils.StringUtils;
import com.xunk.common.redis.service.RedisService;
import com.xunk.equipment.mapper.UhomeAuthDeviceInfoMapper;
import com.xunk.equipment.service.zhijia.constant.ZhijiaConstant;
import lombok.extern.slf4j.Slf4j;
import org.springframework.util.CollectionUtils;

import java.net.MalformedURLException;
import java.security.MessageDigest;
import java.util.List;
import java.util.concurrent.TimeUnit;

/**
 * @ProjectName: HIM
 * @Package: com.xunk.equipment.service.zhijia.util
 * @ClassName: ZhijiaUtil
 * @Author: luanzhiwei
 * @Description: 智家工具类
 * @Date: 2021/4/26 10:22
 * @Version: 1.0
 */
@Slf4j
public class ZhijiaUtil {

    /**
     * 待签名字符串为： url字符串 + Body字符串+appId+appKey +timestamp；
     *
     * @param appId     appId：Header头中的属性（见公共部分说明）；
     * @param appKey    appKey：在海极网给应用申请的appKey，不能明文发送；
     * @param timestamp timestamp：Header头中的属性（见公共部分说明）；
     * @param body      Body字符串：指应用发送请求的Body部分去除所有空白字符后的JSON字符串，没有body时为空字符串（不是null也不是{}）。
     * @param url       url字符串：指请求的接口地址去除https://uws.haier.net 后剩余的路径部分；
     * @return
     * @throws MalformedURLException
     */
    public static String signHttp(String appId, String appKey, String timestamp, String body, String url) {
        appKey = appKey.trim();
        appKey = appKey.replaceAll("\"", "");
        if (body != null) {
            body = body.trim();
        }
        if (StringUtils.isNotEmpty(body)) {
            body = body.replaceAll(" ", "");
            body = body.replaceAll("\t", "");
            body = body.replaceAll("\r", "");
            body = body.replaceAll("\n", "");
        }
        StringBuffer sb = new StringBuffer();
        sb.append(url).append(body).append(appId).append(appKey).append(timestamp);
        log.info("signBody -> {}", body);
        log.info("signStr -> {}", sb);
        MessageDigest md;
        byte[] bytes = null;
        try {
            md = MessageDigest.getInstance("SHA-256");
            bytes = md.digest(sb.toString().getBytes("utf-8"));
        } catch (Exception e) {
            e.printStackTrace();
        }

        return binaryToHexString(bytes);
    }


    /**
     * 参数意义同{@link ZhijiaUtil#signHttp(String, String, String, String, String)}
     *
     * @param systemId
     * @param systemKey
     * @param timestamp
     * @return
     */
    public static String signSocket(String systemId, String systemKey, String timestamp) {
        systemKey = systemKey.trim();
        systemKey = systemKey.replaceAll("\"", "");

        StringBuffer sb = new StringBuffer();
        sb.append(systemId).append(systemKey).append(timestamp);
        MessageDigest md = null;
        byte[] bytes = null;
        try {
            md = MessageDigest.getInstance("SHA-256");
            bytes = md.digest(sb.toString().getBytes("utf-8"));
        } catch (Exception e) {
            e.printStackTrace();
        }
        return binaryToHexString(bytes);
    }


    /**
     * 进制转换
     *
     * @param bytes
     * @return
     */
    public static String binaryToHexString(byte[] bytes) {
        StringBuilder hex = new StringBuilder();
        String hexStr = "0123456789abcdef";
        for (int i = 0; i < bytes.length; i++) {
            hex.append(hexStr.charAt((bytes[i] & 0xF0) >> 4));
            hex.append(hexStr.charAt(bytes[i] & 0x0F));
        }
        return hex.toString();
    }

    /**
     * 查询typeid集合
     *
     * @return
     */
    public static List<String> getTypeIds() {
        final RedisService redisService = SpringUtils.getBean(RedisService.class);
        List<String> typeids = redisService.getCacheList(ZhijiaConstant.TYPE_ID_LIST_KEY);
        if (CollectionUtils.isEmpty(typeids)) {
            final UhomeAuthDeviceInfoMapper mapper = SpringUtils.getBean(UhomeAuthDeviceInfoMapper.class);
            typeids = mapper.selectTypeIds();
            redisService.setCacheList(ZhijiaConstant.TYPE_ID_LIST_KEY, typeids);
            redisService.expire(ZhijiaConstant.TYPE_ID_LIST_KEY, 10, TimeUnit.MINUTES);
        }
        return typeids;
    }
}
